#ifndef _BSP_KEY_H
#define _BSP_KEY_H

#include "stm32f4xx_hal.h"

#define KEY_UP_RCC_CLK_ENABLE()					__HAL_RCC_GPIOA_CLK_ENABLE()
#define KEY_UP_Pin 											GPIO_PIN_0
#define KEY_UP_GPIO_Port 								GPIOA

#define KEY0_RCC_CLK_ENABLE()						__HAL_RCC_GPIOE_CLK_ENABLE()
#define KEY0_Pin 												GPIO_PIN_4
#define KEY0_GPIO_Port 									GPIOE


#define KEY1_RCC_CLK_ENABLE()						__HAL_RCC_GPIOE_CLK_ENABLE()
#define KEY1_Pin 												GPIO_PIN_3
#define KEY1_GPIO_Port 									GPIOE

#define KEY2_RCC_CLK_ENABLE()						__HAL_RCC_GPIOE_CLK_ENABLE()
#define KEY2_Pin 												GPIO_PIN_2
#define KEY2_GPIO_Port 									GPIOE

#define KEY_COUNT 			5			// 定义5组按键,其中一组为组合按键

/* 定义键值代码,顺序固定：按下按下、弹起和长按 */
typedef enum
{
	KEY_NONE = 0,

	KEY_1_DOWN,
	KEY_1_UP,
	KEY_1_LONG,

	KEY_2_DOWN,
	KEY_2_UP,
	KEY_2_LONG,

	KEY_3_DOWN,
	KEY_3_UP,
	KEY_3_LONG,

	KEY_4_DOWN,
	KEY_4_UP,
	KEY_4_LONG,	

	KEY_5_DOWN,
	KEY_5_UP,
	KEY_5_LONG,	
} KEY_ENUM;

/*
	按键滤波时间 50ms,时基10ms
	滤波包含弹起和按下
*/
#define KEY_FILTER_TIME				5
#define KEY_LONG_TIME					100			// 10ms时基，按下超过1s认为是长按

/* 按键对应的功能结构体 */
typedef struct
{
	uint8_t (*IsKeyDownFunc)(void);			// 按键按下的函数指针
	uint8_t Count;											// 滤波计数器
	uint16_t LongCount;									// 长按计数器
	uint16_t LongTime;									// 判定位长按的阈值时间，0表示不检测长按
	uint8_t State;											// 当前按键状态
	uint8_t RepeatSpeed;								// 连续按键周期
	uint8_t RepeatCount;								// 连续按键计数器
} KEY_T;

/* 按键FIFO,最大缓冲按键事件 */
#define KEY_FIFO_SIZE			10
/* 按键FIFO结构体 */
typedef struct
{
	uint8_t Buf[KEY_FIFO_SIZE];			// FIFO的缓冲空间
	uint8_t Read;										// 缓冲区读指针1			
	uint8_t Write;									// 缓冲区写指针
	uint8_t Read2;									// 缓冲区读指针2
} KEY_FIFO_T;


void bsp_InitKey(void);
void bsp_PutKey(uint8_t _KeyCode);
uint8_t bsp_GetKey(void);
uint8_t bsp_GetKey2(void);
void bsp_SetKeyParam(uint8_t _ucKeyID, uint8_t _LongTime, uint8_t _RepeatSpeed);
void Key_Scan(void);


#endif

